package com.cloud.cloudvideo.utils;

import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;



/**
 * 上传 鉴权 转码
 */

public class VideoUtil {

    /**
     * 截图Linux版本
     *
     * @param video_path
     * @param ffmpeg_path
     * @param seconds
     *            /usr/bin/ffmpeg -i /home/jjyy/sun/volume/nginx/html/1/source/20200521/i5AhYdcTcj/i5AhYdcTcj.wmv -y -f image2 -ss 1 -s 800x600 /home/jjyy/sun/volume/nginx/html/1/source/20200521/i5AhYdcTcj/1.jpg
     * @return 返回视频时间
     * @throws Exception
     */
    public static int processImgLinux(String video_path, String ffmpeg_path, int seconds) throws Exception {

        int time = 0;
        File file = new File(video_path);
        if (!file.exists()) {
            System.err.println("路径[" + video_path + "]对应的视频文件不存在!");
            return 0;
        }
        String picPath = file.getParent();
        String imgName = seconds + ".jpg";

        List<String> commands = new java.util.ArrayList<String>();
        commands.add(ffmpeg_path);
        commands.add("-i");
        commands.add(video_path);
        commands.add("-y");
        commands.add("-f");
        commands.add("image2");
        commands.add("-ss");
        commands.add(seconds + "");//这个参数是设置截取视频多少秒时的画面
        //commands.add("-t");
        //commands.add("0.001");
        commands.add("-s");
        commands.add("800x600");
        commands.add(picPath + "/" + imgName);
        StringBuffer test = new StringBuffer();
        for (int i = 0; i < commands.size(); i++)
            test.append(commands.get(i) + " ");
        System.out.println(test);
        try {
            Runtime rt = Runtime.getRuntime();
            Process proc = rt.exec(test.toString());
            InputStream stderr = proc.getErrorStream();
            InputStreamReader isr = new InputStreamReader(stderr);
            BufferedReader br = new BufferedReader(isr);

            StringBuilder stringBuilder = new StringBuilder();
            String line = "";
            while ((line = br.readLine()) != null) {
                stringBuilder.append(line);
            }
            br.close();

            //从视频信息中解析时长
            String regexDuration = "Duration: (.*?), start: (.*?), bitrate: (\\d*) kb\\/s";
            Pattern pattern = Pattern.compile(regexDuration);
            Matcher m = pattern.matcher(stringBuilder.toString());
            if (m.find()) {
                time = getTimelen(m.group(1));
                System.out.println("视频时长：" + time + "s , 开始时间：" + m.group(2) + ", 比特率：" + m.group(3) + "kb/s");
            }
            System.out.println("截取成功");
            return time;

        } catch (IOException e) {
        	e.printStackTrace();
            throw new Exception("截图图片失败");
        }
    }

    /**
     * Linux mp4转码 TS
     *
     * @param video_path  视频路径
     * @param ffmpeg_path ffmpeg路径
     * @return ffmpeg -y -i test.mp4 -vcodec copy -acodec copy -vbsf h264_mp4toannexb test.ts
     * @throws Exception
     */
    public static String transcodingTSByLinux(String video_path, String ffmpeg_path) throws Exception {
        File file = new File(video_path);
        if (!file.exists()) {
            throw new Exception("路径[" + video_path + "]对应的视频文件不存在!");
        }
        String tsPath = file.getParent();
        String tsName = FileUtil.getPrefixOfFileName(video_path) + ".ts";
        List<String> commands = new java.util.ArrayList<>();
        commands.add(ffmpeg_path);
        commands.add("-y");
        commands.add("-i");
        commands.add(video_path);
        commands.add("-vcodec");
        commands.add("copy");
        commands.add("-acodec");
        commands.add("copy");
        commands.add("-vbsf");
        commands.add("h264_mp4toannexb");
        commands.add(tsPath + "/" + tsName);
        StringBuffer test = new StringBuffer();
        for (int i = 0; i < commands.size(); i++)
            test.append(commands.get(i) + " ");
        System.out.println(test);
        try {
            Runtime rt = Runtime.getRuntime();
            Process proc = rt.exec(test.toString());
            InputStream stderr = proc.getErrorStream();
            InputStreamReader isr = new InputStreamReader(stderr);
            BufferedReader br = new BufferedReader(isr);
            String line = null;
            while ((line = br.readLine()) != null) ;

        } catch (IOException e) {
            throw new Exception("转变TS失败");
        }
        return tsPath+ "/" + tsName;
    }

    /**
     * Linux 转码 M3U8
     *
     * @param tsPath      TS视频路径
     * @param ffmpeg_path ffmpeg路径
     * @return  ffmpeg -i 本地视频.ts -c copy -map 0 -f segment -segment_list 视频索引.m3u8 -segment_time 5 前缀-%03d.ts
     * @throws Exception
     */
    public static String transcodingM3U8ByLinux(String tsPath, String ffmpeg_path) throws Exception {
        File file = new File(tsPath);
        if (!file.exists()) {
            throw new Exception("路径[" + tsPath + "]对应的视频文件不存在!");
        }
        String m3u8Path = file.getParent();
        String m3u8Name = FileUtil.getPrefixOfFileName(tsPath) + ".m3u8";
        List<String> commands = new java.util.ArrayList<>();
        commands.add(ffmpeg_path);
        commands.add("-i");
        commands.add(tsPath);
        commands.add("-c");
        commands.add("copy");
        commands.add("-map");
        commands.add("0");
        commands.add("-f");
        commands.add("segment");
        commands.add("-segment_list");
        commands.add(m3u8Path + "/" + m3u8Name);
        commands.add("-segment_time");
        commands.add("2");
        commands.add(m3u8Path + "/niit-%04d.ts");
        StringBuffer test = new StringBuffer();
        for (int i = 0; i < commands.size(); i++)
            test.append(commands.get(i) + " ");
        System.out.println(test);
        try {
            Runtime rt = Runtime.getRuntime();
            Process proc = rt.exec(test.toString());
            InputStream stderr = proc.getErrorStream();
            InputStreamReader isr = new InputStreamReader(stderr);
            BufferedReader br = new BufferedReader(isr);
            String line = null;
            while ((line = br.readLine()) != null) ;

        } catch (IOException e) {
            throw new Exception("转变M3U8失败");
        }
        return m3u8Path+ "/"  + m3u8Name;
    }


    /**
     * 截取视频指定帧windows版本
     *
     * @param video_path
     * @param ffmpeg_path
     * @param seconds
     * @return
     */
    public static int processImgWindows(String video_path, String ffmpeg_path, int seconds) {
        int time = 0;
        File file = new File(video_path);
        if (!file.exists()) {
            System.err.println("路径[" + video_path + "]对应的视频文件不存在!");
            return 0;
        }
        String picPath = file.getParent();
        String imgName = seconds + ".jpg";
        List<String> commands = new java.util.ArrayList<String>();
        commands.add(ffmpeg_path);
        commands.add("-i");
        commands.add(video_path);
        commands.add("-y");
        commands.add("-f");
        commands.add("image2");
        commands.add("-ss");
        commands.add(seconds + "");//这个参数是设置截取视频多少秒时的画面
        //commands.add("-t");
        //commands.add("0.001");
        commands.add("-s");
        commands.add("800x600");
        commands.add(picPath + "/" + imgName);
        try {
            ProcessBuilder builder = new ProcessBuilder();
            builder.command(commands);
            Process p = builder.start();
            BufferedReader br = new BufferedReader(new InputStreamReader(p.getErrorStream()));
            StringBuilder stringBuilder = new StringBuilder();
            String line = "";
            while ((line = br.readLine()) != null) {
                stringBuilder.append(line);
            }
            br.close();

            //从视频信息中解析时长
            String regexDuration = "Duration: (.*?), start: (.*?), bitrate: (\\d*) kb\\/s";
            Pattern pattern = Pattern.compile(regexDuration);
            Matcher m = pattern.matcher(stringBuilder.toString());
            if (m.find()) {
                time = getTimelen(m.group(1));
                System.out.println("视频时长：" + time + "s , 开始时间：" + m.group(2) + ", 比特率：" + m.group(3) + "kb/s");
            }
            System.out.println("截取成功");
            return time;
        } catch (Exception e) {
            e.printStackTrace();
            return 0;
        }
    }
    
    
    
    /**
     * Linux 转码 M3U8
     *
     * @param ffmpeg_path ffmpeg路径
     * @return  ffmpeg -framerate 1 -start_number 0 -i “e:\record\img%3d.jpg” -filter:v scale=1280:720 e:\output2.mp4
     * @throws Exception
     */
    public static String transcodingMp4Windows(String videoPath, String ffmpeg_path) throws Exception {
        File file = new File(videoPath);
        if (!file.exists()) {
            throw new Exception("路径[" + videoPath + "]对应的视频文件不存在!");
        }
        String m3u8Path = file.getParent();
        String m3u8Name = FileUtil.getPrefixOfFileName(videoPath) + ".m3u8";
        List<String> commands = new java.util.ArrayList<>();
        commands.add(ffmpeg_path);
        commands.add("-framerate 1");
        commands.add("-start_number 0");
        commands.add("-i");
        commands.add(videoPath);
        commands.add("-filter:v");
        commands.add("scale=1280:720");
        commands.add(file.getAbsolutePath()+"\\"+file.getName()+"ffmpeg.mp4");
        StringBuffer test = new StringBuffer();
        for (int i = 0; i < commands.size(); i++)
            test.append(commands.get(i) + " ");
        System.out.println(test);
        try {
            Runtime rt = Runtime.getRuntime();
            Process proc = rt.exec(test.toString());
            InputStream stderr = proc.getErrorStream();
            InputStreamReader isr = new InputStreamReader(stderr);
            BufferedReader br = new BufferedReader(isr);
            String line = null;
            while ((line = br.readLine()) != null) ;

        } catch (IOException e) {
            throw new Exception();
        }
        return file.getName()+"ffmpeg.mp4";
    }
    
    
    

    /**
     * @param timelen 格式:"00:00:10.68"
     * @return
     */
    private static int getTimelen(String timelen) {
        int min = 0;
        String strs[] = timelen.split(":");
        if (strs[0].compareTo("0") > 0) {
            // 秒
            min += Integer.valueOf(strs[0]) * 60 * 60;
        }
        if (strs[1].compareTo("0") > 0) {
            min += Integer.valueOf(strs[1]) * 60;
        }
        if (strs[2].compareTo("0") > 0) {
            min += Math.round(Float.valueOf(strs[2]));
        }
        return min;
    }
}
